#Boa:FramePanel:WXVISPANEL

import wx
import os, sys
import shutil
import time
import math
import vtk
import vtktudoss
import superthread
try:
    import extended.BaseCalc as BaseCalc
except ImportError:
    import BaseCalc
import pdb

def create(parent, renderwindow, primaryrenderer):
    return TimeWindowTrace(parent, renderwindow, primaryrenderer)


class TimeWindowTrace:

    def __init__(self, parent, renderwindow, primaryrenderer):
        self.parent = parent
        self.renderwindow = renderwindow.GetRenderWindow()
        #~ self.renX = primaryrenderer
        self.renXannotation = primaryrenderer
        #~ self.InitializeAnnotationLayer()
        self.bluetracelist=[]
        self.yellowtracelist=[]
        
        #~ self.filtertraces_0 = []
        #~ self.filtertraces_1 = []
        #~ self.filtertraces_0_keys = [[]]
        #~ self.filtertraces_1_keys = [[]]
        #~ self.firsttracerpoint_0 = True
        #~ self.firsttracerpoint_1 = True
        
        
    def InitializeAnnotationLayer(self):
        try:
            self.renderwindow.RemoveRenderer(self.renXannotation)
        except AttributeError:
            pass
        self.renderwindow.SetNumberOfLayers(2)
        self.renXannotation = vtk.vtkRenderer()
        self.renX.SetLayer(0)
        self.renXannotation.SetLayer(1)
        self.renXannotation.InteractiveOff()
        self.renXannotation.SetActiveCamera(self.renX.GetActiveCamera())
        self.renderwindow.AddRenderer(self.renXannotation)
        
    def ClearTraces(self, whichone):
        if whichone==0:
            self.ClearBlueTraces()
        else:
            self.ClearYellowTraces()
    
    def ClearBlueTraces(self):
        for trace in self.bluetracelist:
            self.renXannotation.RemoveActor(trace)
        self.bluetracelist[:]=[]
        
    def ClearYellowTraces(self):
        for trace in self.yellowtracelist:
            self.renXannotation.RemoveActor(trace)
        self.yellowtracelist[:]=[]
        
    def DrawTrace(self, whichdata, posenr, window):   
        
        if window == None:
            window = [self.parent.editorpanel.spin_ctrl_1.GetValue(), self.parent.editorpanel.spin_ctrl_2.GetValue()]        
        
        if self.parent.editorpanel.tracercheckbox_1.GetValue():          #traces     
            if self.parent.editorpanel.tracercheckbox_2.GetValue():      #clavicle
                self.DrawJointTrace(whichdata, posenr, 2, window)
                self.DrawJointTrace(whichdata, posenr, 3, window)
                #~ if self.parent.editorpanel.tracercheckbox_1_copy.GetValue():     #surfaces
                    #~ self.ConnectLastTwoTraces()
            if self.parent.editorpanel.tracercheckbox_3.GetValue():      #scapula
                self.DrawJointTrace(whichdata, posenr, 4, window)
                self.DrawJointTrace(whichdata, posenr, 5, window)
                #~ if self.parent.editorpanel.tracercheckbox_1_copy.GetValue():     #surfaces
                    #~ self.ConnectLastTwoTraces()
                #~ self.DrawJointTrace(whichdata, posenr, 6, window)
                self.DrawJointTrace(whichdata, posenr, 7, window)
                #~ if self.parent.editorpanel.tracercheckbox_1_copy.GetValue():     #surfaces
                    #~ self.ConnectLastTwoTraces()
                #~ self.DrawJointTrace(whichdata, posenr, 9, window)
                #~ if self.parent.editorpanel.tracercheckbox_1_copy.GetValue():     #surfaces
                    #~ self.ConnectLastTwoTraces()
            if self.parent.editorpanel.tracercheckbox_4.GetValue():      #humerus
                self.DrawJointTrace(whichdata, posenr, -1, window)
                self.DrawJointTrace(whichdata, posenr, 10, window)
                #~ if self.parent.editorpanel.tracercheckbox_1_copy.GetValue():     #surfaces
                    #~ self.ConnectLastTwoTraces()
            if self.parent.editorpanel.tracercheckbox_5.GetValue():      #forearm
                #~ self.DrawJointTrace(whichdata, posenr, 10, window)
                self.DrawJointTrace(whichdata, posenr, 11, window)
                #~ if self.parent.editorpanel.tracercheckbox_1_copy.GetValue():     #surfaces
                    #~ self.ConnectLastTwoTraces()
        
    def ConnectLastTwoTraces(self):
        input1 = self.tracelist[len(self.tracelist)-1].GetMapper().GetInput()
        input2 = self.tracelist[len(self.tracelist)-2].GetMapper().GetInput()

        #~ appendFilter2 = vtk.vtkAppendFilter()
        #~ appendFilter2.AddInput(input1.GetPointData())
        #~ appendFilter2.AddInput(input2.GetPointData())
        #~ appendFilter2.Update()
        print input1
        print input2
        
        newpolydata = vtk.vtkPolyData()
        newpointdata = vtk.vtkPoints()
        newcelldata = vtk.vtkCellArray()
        
        appendFilter = vtk.vtkAppendFilter()
        appendFilter.AddInput(input1)
        appendFilter.AddInput(input2)
        appendFilter.Update()
        print appendFilter.GetOutput()
        
        nrofpoints = input1.GetPoints().GetNumberOfPoints()
        for i in range(0, nrofpoints-1):
            newcelldata.InsertNextCell(4)
            newcelldata.InsertCellPoint(i)
            newcelldata.InsertCellPoint(i+1)
            newcelldata.InsertCellPoint(i+1 + nrofpoints)
            newcelldata.InsertCellPoint(i      + nrofpoints)
  
        newpolydata.SetPoints(appendFilter.GetOutput().GetPoints())
        newpolydata.SetPolys(newcelldata)
        newpolydata.GetPointData().SetActiveScalars("woosh")                                
        newpolydata.Update()     
        
        tracemapper = vtktudoss.vtktudExtendedOpenGLPolyDataMapper()
        traceactor = vtk.vtkActor()
        traceactor.SetMapper(tracemapper)
        tracemapper.SetInput(newpolydata)
        tracemapper.SetUseLookupTableScalarRange(1)
        tracemapper.InterpolateScalarsBeforeMappingOn()
        tracemapper.SetScalarModeToUsePointData()
        tracemapper.SetScalarMaterialModeToAmbient()
        tracemapper.SetLookupTable(self.parent.parent.colorscales.LUT_Woosh)
        tracemapper.ScalarVisibilityOn()
        #~ traceactor.GetProperty().SetSpecular(.0)
        #~ traceactor.GetProperty().SetDiffuse(.1)
        #~ traceactor.GetProperty().SetAmbient(.5)
        #~ traceactor.GetProperty().SetSpecularPower(0)
        self.renXannotation.AddActor(traceactor)
        
        self.tracelist.append(traceactor)
        
        
    def DrawJointTrace(self, whichdata, posenr, vertexnr, window):
        newpolydata = vtk.vtkPolyData()
        newpointdata = vtk.vtkPoints()
        newcelldata = vtk.vtkCellArray()
        poseColors = vtk.vtkFloatArray() 
        poseColors.SetName("woosh")        
        
        base = posenr
        
        if whichdata == 0:
            numberofposes = len(self.parent.parent.splineCollection)
        else:
            numberofposes = len(self.parent.parent.splineReferences)

        for i in range(0, -window[0]):
            item = base - i
            if item >= 0:
                if whichdata == 0:
                    if vertexnr!=-1:
                        newpointdata.InsertNextPoint(\
                                self.parent.parent.splineCollection[item]['poseActor'].\
                                GetMapper().GetInput().GetPoints().\
                                GetPoint(vertexnr))
                    else:
                        tr1 = self.parent.parent.splineCollection[item]['shadedArm'].GetUserTransform()
                        point = tr1.TransformFloatPoint(\
                                self.parent.parent.splineCollection[item]['shadedArm'].\
                                GetMapper().GetInput().GetPoints().\
                                GetPoint(0))
                        newpointdata.InsertNextPoint(point)
                else:
                    if vertexnr!=-1:
                        newpointdata.InsertNextPoint(\
                                self.parent.parent.splineReferences[item]['poseActor'].\
                                GetMapper().GetInput().GetPoints().\
                                GetPoint(vertexnr))
                    else:
                        tr1 = self.parent.parent.splineReferences[item]['shadedArm'].GetUserTransform()
                        point = tr1.TransformFloatPoint(\
                                self.parent.parent.splineReferences[item]['shadedArm'].\
                                GetMapper().GetInput().GetPoints().\
                                GetPoint(0))
                        newpointdata.InsertNextPoint(point)

        nrofpoints_back = newpointdata.GetNumberOfPoints()

        for i in range(0, window[1]):
            item = base + i
            if item <= numberofposes:
                if whichdata == 0:
                    if vertexnr!=-1:
                        newpointdata.InsertNextPoint(\
                                self.parent.parent.splineCollection[item]['poseActor'].\
                                GetMapper().GetInput().GetPoints().\
                                GetPoint(vertexnr))
                    else:
                        tr1 = self.parent.parent.splineCollection[item]['shadedArm'].GetUserTransform()
                        point = tr1.TransformFloatPoint(\
                                self.parent.parent.splineCollection[item]['shadedArm'].\
                                GetMapper().GetInput().GetPoints().\
                                GetPoint(0))
                        newpointdata.InsertNextPoint(point)
                else:
                    if vertexnr!=-1:
                        newpointdata.InsertNextPoint(\
                                self.parent.parent.splineReferences[item]['poseActor'].\
                                GetMapper().GetInput().GetPoints().\
                                GetPoint(vertexnr))
                    else:
                        tr1 = self.parent.parent.splineReferences[item]['shadedArm'].GetUserTransform()
                        point = tr1.TransformFloatPoint(\
                                self.parent.parent.splineReferences[item]['shadedArm'].\
                                GetMapper().GetInput().GetPoints().\
                                GetPoint(0))
                        newpointdata.InsertNextPoint(point)

        aSplineX = vtk.vtkCardinalSpline()
        aSplineY = vtk.vtkCardinalSpline()
        aSplineZ = vtk.vtkCardinalSpline()
        numberOfInputPoints = newpointdata.GetNumberOfPoints()
        for i in range(0, numberOfInputPoints):
            point = newpointdata.GetPoint(i)
            aSplineX.AddPoint(i, point[0])
            aSplineY.AddPoint(i, point[1])
            aSplineZ.AddPoint(i, point[2])
        interpolatedpointdata = vtk.vtkPoints()
        numberOfOutputPoints = numberOfInputPoints * 4
        
        totalbackpoints = float(nrofpoints_back*4)
        totalfrontpoints = float(numberOfInputPoints*4-(nrofpoints_back*4))
        for i in range(0, numberOfOutputPoints):
            t = (numberOfInputPoints-1.0)/(numberOfOutputPoints-1.0)*i
            interpolatedpointdata.InsertPoint(i, aSplineX.Evaluate(t),\
                                        aSplineY.Evaluate(t),aSplineZ.Evaluate(t))
            if i <= nrofpoints_back*4:
                poseColors.InsertTuple1(i, (i/totalbackpoints)*20)
            else:
                poseColors.InsertTuple1(i, ((i-totalbackpoints)/totalfrontpoints)*20.0)
        
        for i in range(0, numberOfOutputPoints-1):
            newcelldata.InsertNextCell(2)
            newcelldata.InsertCellPoint(i)
            newcelldata.InsertCellPoint(i+1)
                
        newpolydata.SetPoints(interpolatedpointdata)
        newpolydata.SetLines(newcelldata)
        newpolydata.GetPointData().AddArray(poseColors)
        newpolydata.GetPointData().SetActiveScalars("woosh")                        
        newpolydata.Update()        
        tracemapper = vtktudoss.vtktudExtendedOpenGLPolyDataMapper()
        traceactor = vtk.vtkActor()
        traceactor.SetMapper(tracemapper)
        tracemapper.SetInput(newpolydata)
        tracemapper.SetUseLookupTableScalarRange(1)
        if whichdata==0:
            tracemapper.SetLookupTable(self.parent.parent.colorscales.LUT_WooshBlue)
        else:
            tracemapper.SetLookupTable(self.parent.parent.colorscales.LUT_WooshYellow)
        tracemapper.ScalarVisibilityOn()
        self.renXannotation.AddActor(traceactor)
        
        if whichdata==0:
            self.bluetracelist.append(traceactor)
        else:
            self.yellowtracelist.append(traceactor)
        

    #~ def AddTraceFrame(self, whichdata, poseActor, splineNr):           
        #~ if self.parent.editorpanel.tracercheckbox_5.GetValue():      #forearm
            #~ self.AddSinglePoint(whichdata, poseActor, 11, splineNr)
        
    #~ def AddSinglePoint(self, whichdata, poseActor, vertexnr, splineNr):
        #~ if whichdata == 0 and self.firsttracerpoint_0 == True:
            #~ newpolydata = vtk.vtkPolyData()
            #~ newpointdata = vtk.vtkPoints()
            #~ newcelldata = vtk.vtkCellArray()
            #~ newpolydata.SetPoints(newpointdata)
            #~ newpolydata.SetLines(newcelldata)           
            #~ newpolydata.Update()                             
            #~ tracemapper = vtktud.vtktudExtendedOpenGLPolyDataMapper()
            #~ traceactor = vtk.vtkActor()
            #~ traceactor.SetMapper(tracemapper)
            #~ tracemapper.SetInput(newpolydata)
            #~ self.filtertraces_0.append(traceactor)            
            #~ self.renXannotation.AddActor(traceactor)
            #~ self.firsttracerpoint_0 = False
        
        #~ self.filtertraces_0_keys[-1].append(splineNr)
        
        #~ if whichdata == 0:
            #~ self.filtertraces_0[-1].GetMapper().GetInput().GetPoints().InsertNextPoint(\
                        #~ poseActor.GetMapper().GetInput().GetPoints().\
                        #~ GetPoint(vertexnr))
            #~ nrofpoints = self.filtertraces_0[-1].GetMapper().GetInput().GetPoints().GetNumberOfPoints()
            #~ if nrofpoints>1:
                #~ self.filtertraces_0[-1].GetMapper().GetInput().GetLines().InsertNextCell(2)
                #~ self.filtertraces_0[-1].GetMapper().GetInput().GetLines().InsertCellPoint(nrofpoints-1)
                #~ self.filtertraces_0[-1].GetMapper().GetInput().GetLines().InsertCellPoint(nrofpoints)
            #~ self.filtertraces_0[-1].GetMapper().Update()
                    
    #~ def TerminateTrace(self, whichdata, splineNr):
        #~ if whichdata == 0:
            #~ for i in range(0, len(self.filtertraces_0_keys)):
                #~ if splineNr in self.filtertraces_0_keys[i]:
                    #~ self.renXannotation.RemoveActor(self.filtertraces_0[i])
                    #~ self.filtertraces_0.pop(i)
                    #~ self.filtertraces_0_keys.pop(i)
                    #~ i = i -1
            #~ self.firsttracerpoint_0 = True
            #~ try:
                #~ if self.filtertraces_0_keys[-1] != []:
                    #~ self.filtertraces_0_keys.append([])
            #~ except IndexError:
                #~ self.filtertraces_0_keys.append([])